import React, { useState, useEffect, useCallback, useRef } from 'react';
import Search from 'antd/lib/input/Search';
import { Space, Button, Table, message, Tooltip, Upload, Alert } from 'antd';

import { ColumnsType } from 'antd/lib/table';
import { getSoundRecordList, uploadSoundRecord } from 'admin/servers/servers';
import { SoundRecordInfo } from 'admin/schema/SoundLibrary';
import {
  AudioOutlined,
  DownloadOutlined,
  PlayCircleOutlined,
  PlayCircleTwoTone,
  QuestionCircleFilled,
  UploadOutlined,
} from '@ant-design/icons';
import SoundRecord from './SoundRecord';
import { MultipleUploadPop } from './MultipleUploadPop';
import { debounce } from 'lodash';

interface IProps {
  templateId: number; //模板id
  type: 'ai' | 'notice'; //模板类型 "ai" | "notice"
  containVar: number; //是否包含变量
  refreshPane: () => void; // 更新模板列表数据
}

/**
 * 录音模板-话术列表
 * AI管理-机器人管理-版本管理-配置话术流程-录音模板-话术列表
 *
 */
const SoundList: React.FC<IProps> = ({ templateId, type, containVar, refreshPane }) => {
  /**
   * 在线录音弹窗-ref
   */
  const childRef = useRef();
  /**
   * loading上传中-ref
   */
  const loadingsRef = useRef<Array<number>>([]);
  /**录音播放-ref */
  const audioRef = useRef<any>(undefined);
  /**
   * 批量上传录音弹窗-ref
   */
  const multipleUploadRef = useRef();
  // Table loading状态
  const [tableLoading, setTableLoading] = useState<boolean>(false);
  // 当前页码
  const [current, setCurrent] = useState<number>(1);
  // 每页条数
  const [pageSize, setPageSize] = useState<number>(10);
  // 数据总数
  const [total, setTotal] = useState<number>(0);
  // 文件下载路径
  const [downloadPath, setDownloadPath] = useState<string>('');

  const [uploadFile, setUploadFile] = useState<string>('');

  // 搜索内容
  const [searchText, setSearchText] = useState<string>('');
  // table列表数据
  const [soundRecord, setSoundRecord] = useState<SoundRecordInfo[]>([]);

  /**
   * 查询录音库-右侧table数据
   * @param isTableFresh 是否完成上传，完成则刷新页面
   */
  const initData = useCallback(async () => {
    setTableLoading(true);
    try {
      const res = await getSoundRecordList({
        templateId,
        pageNo: current,
        pageSize: type === 'notice' ? 10000 : pageSize, // 通知流程无需翻页，固定一个值-10000
        scriptContent: searchText,
      });
      console.log('模板话术表格--', templateId, res);
      const { code, data, count, tips } = res;
      if (code === 0) {
        setTotal(Number(count) || 0);
        if (data && data.list) {
          const d = data.list;
          // 渲染话术表格
          setSoundRecord(d);
        }
        if (data && data.filePath) {
          const path = (process.env.REACT_APP_API_URL || '') + data.filePath;
          // note：本地测试录音播放
          // let path = "https://znwh.19pay.com.cn" + data.filePath;
          setDownloadPath(path);
        }
      } else {
        message.error(`${tips}(错误码: ${code})`);
      }
    } catch (error) {
      console.error(`系统异常: ${JSON.stringify(error)}`);
    }
    setTableLoading(false);
  }, [current, pageSize, searchText, templateId, type]);

  useEffect(() => {
    initData();
  }, [initData]);

  const refreshSoundPaneList = () => {
    // 判断是否要更新模板列表,话术表格
    // 注意：后端数据是待上传放在列表前面，第一页如果全部上传完就代表所有上传完，第一页有待上传状态，则代表模板未上传完
    getSoundRecordList({
      templateId,
      pageNo: 1,
      pageSize: type === 'notice' ? 10000 : pageSize, // 通知流程无需翻页，固定一个值-10000
      scriptContent: searchText,
    })
      .then(res => {
        const { code, data } = res;
        if (code === 0) {
          if (data && data.list) {
            const d = data.list;
            const rt = d.some((item: SoundRecordInfo) => {
              if (item.status === 0) {
                // 录音模板-话术第一页-存在“待上传的行”
                return true;
              } else {
                // 录音模板-全部上传完毕，更新模板列表。
                return false;
              }
            });
            if (!rt) {
              console.log('需要刷新模板列表', templateId);
              // 更新模板列表
              refreshPane();
            }
            // setTimeout(() => {
            d.map((item: any) => {
              // 正在上传的数据，添加loading
              const index = loadingsRef.current.indexOf(item.soundRecordId);
              if (index >= 0) {
                item.loading = true;
              }
              return null;
            });
            console.log('刷新话术列表-', loadingsRef.current);
            // 渲染话术表格
            setCurrent(1);
            setSoundRecord(d);
            // }, 0);
          }
        }
      })
      .catch(error => {
        console.error(`系统异常: ${JSON.stringify(error)}`);
        clearLoadings();
      });
    // 更新模板列表（包含更新table）
    // 更新table
  };
  /**
   * 清空上传中数组，清空上传状态
   */
  function clearLoadings() {
    loadingsRef.current = [];
    const arr = [...soundRecord];
    arr.map((item: any) => {
      if (item.loading === true) {
        item.loading = false;
      }
      return null;
    });
    setSoundRecord(arr);
  }
  /**
   * 搜索录音模板-话术列表
   * @param text 搜索内容
   */
  const handleSearch = (text: string) => {
    text = text.trim();
    if (text !== searchText) {
      setSearchText(text);
      setCurrent(1);
    }
  };
  /**批量上传 */
  const handleUploadMul = () => {
    (multipleUploadRef.current as any).open(null, () => {
      // 回调函数：操作成功，刷新列表
      refreshSoundPaneList();
    });
  };
  /**
   * 话术列表-上传校验
   * @param id 话术id
   */
  const beforeUpload = (file: any) => {
    const fileName = file.name.split('.');
    const type = file.type;

    const isWav = (type && type.indexOf('wav') > -1) || fileName[fileName.length - 1] === 'wav';
    const isLt50M = file.size / 1024 / 1024 < 50;
    if (!isWav) {
      message.error('请上传wav文件（只支持wav格式）!');
      return false;
    }
    if (!isLt50M) {
      message.error('文件大小超过50M!');
      return false;
    }
    setUploadFile(file);
    return true;
  };

  /**
   * 话术列表-上传录音
   * @param soundRecordId 话术id
   */
  const handleUpload = (soundRecordId: number) => {
    // if (loadings.length > 0) {
    //   message.warning("当前模板正在上传文件，请稍后重试");
    //   return false;
    // }
    // 加入ref数组
    loadingsRef.current.push(soundRecordId);
    console.log(soundRecordId + '加入上传', loadingsRef.current);
    // 添加loading状态
    const arr = [...soundRecord];
    arr.map((item: any) => {
      if (item.soundRecordId === soundRecordId) {
        item.loading = true;
      }
      return null;
    });
    setSoundRecord(arr);
    console.log('1.开始上传录音文件', uploadFile);
    const formData = new FormData();
    formData.append('file', uploadFile);
    formData.append('templateId', JSON.stringify(templateId));

    // 接口
    uploadSoundRecord(soundRecordId, formData)
      .then(res => {
        if (res.code === 0) {
          message.success('上传成功！');
          // 从ref中删除
          const index = loadingsRef.current.indexOf(soundRecordId);
          console.log(index, '当前id在ref中的索引');
          if (index >= 0) {
            loadingsRef.current.splice(index, 1);
          }
          console.log(soundRecordId + '上传成功--剩余-当前上传中', loadingsRef.current);
          // 更新页面
          refreshSoundPaneList();
        } else {
          message.error(`${res.tips}(错误码: ${res.code})`);
        }
      })
      .catch(error => {
        console.error(`系统异常: ${JSON.stringify(error)}`);
        clearLoadings();
      });
  };

  /**
   * 录音话术列表-录音
   * step1.开始录音-录音完成-保存重录音-上传-关闭录音弹窗
   * step2.开始录音-重录，返回step1
   * step3.取消，关闭录音弹窗
   * @param id 话术id
   */
  const handleRecord = (record: SoundRecordInfo) => {
    console.log('文件录音', record.soundRecordId);
    (childRef.current as any).open(record, () => {
      // 回调函数：操作成功，刷新列表
      refreshSoundPaneList();
    });
  };

  /**
   * 话术列表-播放
   */

  const handlePlay = (record: any) => {
    // if (record.playing) {
    //   message.info("播放进行中，请勿重复点击");
    //   return false;
    // }
    // 清除-状态

    const id = record.soundRecordId;
    const soundUrl: string = downloadPath + `${record.scriptSign}.wav`;
    // 当前存在正在播放的录音，直接切换播放地址
    console.log('即将播放：', id, soundUrl);
    // 时间戳，防止一直播放的是第一段音频
    const url = soundUrl + '?timestamp=' + new Date().getTime();
    if (!audioRef.current) {
      // 当前没有正在播放的录音
      audioRef.current = new Audio();
      // 绑定-播放暂停事件
      audioRef.current.onpause = () => {
        // 清除-状态
        console.log('播放暂停');
      };
      // 绑定-播放结束事件
      audioRef.current.onended = () => {
        message.info('播放结束');
        clearPlayings();
      };
      // 播放出错
      audioRef.current.onerror = () => {
        message.error('抱歉，播放出错了，请联系管理员~');
        clearPlayings();
      };
    }
    // 暂停播放
    audioRef.current.pause();
    // 切url--开始播放--最后的语音
    audioRef.current.src = url;
    // 开始播放
    audioRef.current.play();
    // 更新播放状态
    const arr = [...soundRecord];
    arr.map((item: any) => {
      if (item.soundRecordId === id) {
        item.playing = true;
      } else {
        item.playing = false;
      }
      return null;
    });
    setSoundRecord(arr);
  };

  /**
   * 清空上传中数组，清空上传状态
   */
  function clearPlayings() {
    audioRef.current = undefined;
    const arr = [...soundRecord];
    arr.map((item: any) => {
      if (item.playing === true) {
        item.playing = false;
      }
      return null;
    });
    setSoundRecord(arr);
  }

  /**
   * Table列描述数据对象
   */
  const renderScriptContent = (text: any, record: any, index: number) => {
    const scripts: Array<string> = record.originalScripts || '';
    return (
      <Tooltip
        placement="topLeft"
        title={
          <>
            {scripts.length > 0 &&
              scripts.map((item, num) => {
                if (num < 5) {
                  return (
                    <div key={num}>
                      <div>原文：{item}</div>
                    </div>
                  );
                } else {
                  return null;
                }
              })}
            {!scripts && <div key={index}>原文：{text}</div>}
          </>
        }
      >
        {text}
      </Tooltip>
    );
  };
  const statusTitle = (
    <div>
      状态&nbsp;
      <Tooltip
        overlayStyle={{ maxWidth: 500 }}
        placement="bottomRight"
        arrowPointAtCenter
        title={
          <div>
            <div>待上传：对应话术没有录音文件，需要上传录音文件</div>
            <div>已上传：录音已经上传，可以被正常使用</div>
          </div>
        }
      >
        <QuestionCircleFilled style={{ fontSize: 16 }} />
      </Tooltip>
    </div>
  );

  const renderScriptSource = (text: any, record: any, index: number) => {
    const flow_arr: Array<string> = JSON.parse(text).flow;
    const question_arr: Array<string> = JSON.parse(text).questionAnswer;
    const flow = flow_arr ? flow_arr.join(',') : '';
    const question = question_arr ? question_arr.join(',') : '';
    return (
      <>
        {
          <Tooltip
            placement="topLeft"
            title={
              <div>
                {flow && <div>组件-{flow}</div>}
                {question && <div>问题-{question}</div>}
              </div>
            }
          >
            {flow && <span>组件-{flow}</span>}
            {flow && question && <br></br>}
            {question && <span>问题-{question}</span>}
          </Tooltip>
        }
      </>
    );
  };

  const renderStatus = (text: any, record: any, index: number) => (
    <>
      {text === 0 && <span style={{ color: 'red' }}>待上传</span>}
      {text === 1 && <span>已上传</span>}
    </>
  );

  const renderAction = (text: any, record: any, index: number) => (
    <Space size="small">
      <Tooltip placement="top" title="播放">
        <Button
          type="link"
          icon={
            record.playing ? <PlayCircleTwoTone twoToneColor="#52c41a" /> : <PlayCircleOutlined />
          }
          disabled={record.status === 1 ? false : true}
          onClick={debounce(() => {
            handlePlay(record);
          }, 700)}
        ></Button>
      </Tooltip>
      <Tooltip placement="top" title="上传">
        <Upload
          name="file"
          accept="audio/wav"
          showUploadList={false}
          multiple={false}
          beforeUpload={(file: any) => {
            return beforeUpload(file);
          }}
          customRequest={() => handleUpload(record.soundRecordId)}
          disabled={record.loading}
        >
          <Button
            type="link"
            icon={<UploadOutlined />}
            loading={record.loading}
            disabled={record.status !== 2 ? false : true}
          ></Button>
        </Upload>
      </Tooltip>
      <Tooltip placement="top" title="录音">
        <Button
          type="link"
          icon={<AudioOutlined />}
          onClick={() => handleRecord(record)}
          disabled={record.status !== 2 ? false : true}
        ></Button>
      </Tooltip>
      <Tooltip placement="top" title="下载">
        <Button
          type="link"
          icon={<DownloadOutlined />}
          href={downloadPath + `${record.scriptSign}.wav`}
          disabled={record.status === 1 ? false : true}
        ></Button>
      </Tooltip>
    </Space>
  );

  // 机器人流程-录音库
  const columnsAi: ColumnsType<SoundRecordInfo> = [
    {
      title: '序号',
      key: 'index',
      width: 100,
      render: (text, record, index) => index + 1 + pageSize * (current - 1),
    },
    {
      title: '话术',
      dataIndex: 'scriptContent',
      key: 'scriptContent',
      ellipsis: {
        showTitle: false,
      },
      render: renderScriptContent,
    },
    {
      title: '话术ID',
      width: 130,
      dataIndex: 'soundRecordId',
      key: 'soundRecordId',
    },
    {
      title: '来源',
      dataIndex: 'scriptSource',
      key: 'scriptSource',
      width: 200,
      ellipsis: {
        showTitle: false,
      },
      render: renderScriptSource,
    },
    {
      title: statusTitle,
      width: 100,
      dataIndex: 'status',
      key: 'status',
      render: renderStatus,
    },
    {
      title: '操作',
      key: 'operation',
      dataIndex: 'operation',
      width: 200,
      render: renderAction,
    },
  ];

  // 通知流程-录音库
  const columnsNotice: ColumnsType<SoundRecordInfo> = [
    {
      title: '序号',
      key: 'index',
      width: 100,
      render: (text, record, index) => index + 1 + pageSize * (current - 1),
    },
    {
      title: '话术',
      dataIndex: 'scriptContent',
      key: 'scriptContent',
      ellipsis: {
        showTitle: false,
      },
      render: renderScriptContent,
    },
    {
      title: statusTitle,
      dataIndex: 'status',
      key: 'status',
      width: 100,
      render: renderStatus,
    },
    {
      title: '操作',
      key: 'action',
      dataIndex: 'action',
      width: 200,
      render: renderAction,
    },
  ];

  return (
    <>
      <div className={type === 'ai' ? 'sound-list-top mgr-header' : 'sound-list-top'}>
        <div className="mgr-header-left">
          {type === 'ai' && (
            <Search
              className="sound-search"
              placeholder="请输入话术内容"
              enterButton="搜索"
              style={{ width: 300, marginRight: '10px' }}
              onSearch={value => handleSearch(value.trim())}
            />
          )}
          {!!containVar && (
            <div className="sound-tip">
              <Alert
                message="含变量的话术已被拆分多段话术，需要分成多段录音上传，鼠标hover到话术能查看原文"
                type="warning"
                showIcon
                closable
              />
            </div>
          )}
        </div>
        {type === 'ai' && (
          <div className="mgr-header-right">
            <Button type="primary" onClick={handleUploadMul}>
              批量上传录音
            </Button>
          </div>
        )}
      </div>
      <div className="sound-list-table">
        {type === 'ai' ? (
          <Table
            loading={tableLoading}
            columns={columnsAi}
            dataSource={soundRecord}
            rowKey={record => record.soundRecordId}
            pagination={{
              current: current,
              total: total,
              pageSize: pageSize,
              showSizeChanger: true,
              // 改条数/页
              onShowSizeChange: (current, size) => {
                setPageSize(size);
              },
              // 改页码
              onChange: current => {
                setCurrent(current);
                clearPlayings();
                clearLoadings();
              },
              showTotal: total => `共${total}条`,
            }}
          />
        ) : (
          <Table
            loading={tableLoading}
            columns={columnsNotice}
            dataSource={soundRecord}
            rowKey={record => record.soundRecordId}
            pagination={false}
          />
        )}
      </div>
      <SoundRecord cRef={childRef} templateId={templateId}></SoundRecord>
      <MultipleUploadPop cRef={multipleUploadRef} templateId={templateId}></MultipleUploadPop>
    </>
  );
};

export default SoundList;
